using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using Apache.Cassandra;


namespace Cassandraemon
{


	public class CassandraQueryable<T> : IOrderedQueryable<T>
	{
		public CassandraContext Context { get { return (Provider as CassandraQueryProvider).Context; } }
		
		public Expression Expression { get; private set; }
		
		public IQueryProvider Provider { get; private set; }
		
		public Type ElementType { get { return typeof(T); } }
		
		
		public CassandraQueryable(){}
		
		public CassandraQueryable(CassandraContext context) 
		{ 
			Provider = new CassandraQueryProvider();
			Expression = Expression.Constant(this);
			
			(Provider as CassandraQueryProvider).Context = context;
		}
		
		public CassandraQueryable(CassandraQueryProvider provider, Expression expression)
		{
			if(provider == null)
			{
				throw new ArgumentNullException("provider");
			}
			
			if(expression == null)
			{
				throw new ArgumentNullException("expression");
			}
			
			if(!typeof(IQueryable<T>).IsAssignableFrom(expression.Type))
			{
				throw new ArgumentOutOfRangeException("expression");
			}
			
			Provider = provider;
			Expression = expression;
		}
		
		
		public IEnumerator<T> GetEnumerator()
		{
			return (Provider.Execute<IEnumerable<T>>(Expression)).GetEnumerator();
		}
		
		System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
		{
			return (Provider.Execute<System.Collections.IEnumerable>(Expression)).GetEnumerator();
		}
		
		
		
		public void InsertOnSubmit(T entity)
		{
			Context.InsertOnSubmit<T>(entity);
		}
		
		public void DeleteOnSubmit(Expression<Func<T, bool>> expression)
		{
			Context.DeleteOnSubmit(expression);
		}
		
	}
}
